package media

import (
	"fmt"
	"os"
	"path/filepath"
	"strings"
	"ytDownload/entity"
	"ytDownload/logger"
	"ytDownload/utils/cmd"
)

type MediaStruct struct {
	name      string
	videoPath string
	audioPath string
}

func merge() {
	saveDir := entity.GetSaveDir()

	mediaMap := make(map[string]*MediaStruct)
	mediaNameArr := []string{}

	err := filepath.Walk(saveDir, func(path string, info os.FileInfo, err error) error {
		if err != nil {
			return err
		}

		if !info.IsDir() {
			// 是文件，获取文件名，放入 map
			name := info.Name()
			logger.Infof("找到文件[%s]", name)
			fileName := ""
			isVideo := false
			isAudio := false
			if strings.HasSuffix(name, "_tv.mp4") {
				// 获取文件名
				fileName = strings.TrimSuffix(name, "_tv.mp4")
				isVideo = true
			} else if strings.HasSuffix(name, "_ta.m4a") {
				// 获取文件名
				fileName = strings.TrimSuffix(name, "_ta.m4a")
				isAudio = true
			}
			logger.Infof("文件名[%s]", fileName)

			if len(fileName) > 0 {

				if mediaMap[fileName] == nil {
					mediaNameArr = append(mediaNameArr, fileName)
					mediaMap[fileName] = &MediaStruct{
						name:      fileName,
						videoPath: "",
						audioPath: "",
					}
				}
				if isVideo {
					mediaMap[fileName].videoPath = path
				}
				if isAudio {
					mediaMap[fileName].audioPath = path
				}
			}

		}

		return nil
	})

	if err != nil {
		panic(err)
	}

	startIdx := 5
	endIdx := 100
	if endIdx > len(mediaNameArr) {
		endIdx = len(mediaNameArr)
	}
	mediaNameArr = mediaNameArr[startIdx:endIdx]

	for _, mediaName := range mediaNameArr {
		media := mediaMap[mediaName]
		mergePath := entity.GetMergeOutputDir()

		err = mergeVideoAudio(media, mergePath)
		if err != nil {
			logger.Errorf("[%s]合并视频和音频失败:%v", mediaName, err)
			continue
		}
		logger.Infof("[%s]合并完成", mediaName)
	}

}

func mergeVideoAudio(media *MediaStruct, mergePath string) (err error) {
	// ffmpeg -i "[audioPath]" -i "[videoPath]" -c copy "[MergePath]"
	err = nil

	if media == nil || media.name == "" ||
		media.audioPath == "" || media.videoPath == "" {
		logger.Errorf("参数错误")
		return fmt.Errorf("参数错误")
	}

	// 检查源文件是否存在
	stat, err := os.Stat(media.audioPath)
	if err != nil || stat.IsDir() {
		logger.Errorf("Audio源文件不存在")
		return fmt.Errorf("audio源文件不存在")
	}

	stat, err = os.Stat(media.videoPath)
	if err != nil || stat.IsDir() {
		logger.Errorf("Video源文件不存在")
		return fmt.Errorf("video源文件不存在")
	}

	logger.Infof("[%s]开始合并视频和音频", media.name)

	_, err = cmd.ExecuCmd("ffmpeg", "-i", media.audioPath,
		"-i", media.videoPath, "-c", "copy", filepath.Join(mergePath, media.name+".mp4"))
	if err != nil {
		logger.Errorf("合并视频和音频失败:%v", err)
		return fmt.Errorf("合并视频和音频失败:%v", err)
	}

	return nil
}
